home *** CD-ROM | disk | FTP | other *** search
/ Chip 2007 January, February, March & April / Chip-Cover-CD-2007-02.iso / Pakiet internetowy / Przegladarki internetowe / Mozilla Seamonkey 1.0.5 pl / seamonkey-1.0.5.pl-PL.win32.installer.exe / VENKMAN.XPI / bin / chrome / venkman.jar / content / venkman / venkman-profiler.js < prev    next >
Encoding:
JavaScript  |  2005-08-02  |  13.6 KB  |  404 lines

  1. /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
  2.  *
  3.  * ***** BEGIN LICENSE BLOCK *****
  4.  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
  5.  *
  6.  * The contents of this file are subject to the Mozilla Public License Version
  7.  * 1.1 (the "License"); you may not use this file except in compliance with
  8.  * the License. You may obtain a copy of the License at
  9.  * http://www.mozilla.org/MPL/
  10.  *
  11.  * Software distributed under the License is distributed on an "AS IS" basis,
  12.  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
  13.  * for the specific language governing rights and limitations under the
  14.  * License.
  15.  *
  16.  * The Original Code is The JavaScript Debugger.
  17.  *
  18.  * The Initial Developer of the Original Code is
  19.  * Netscape Communications Corporation.
  20.  * Portions created by the Initial Developer are Copyright (C) 1998
  21.  * the Initial Developer. All Rights Reserved.
  22.  *
  23.  * Contributor(s):
  24.  *   Robert Ginda, <rginda@netscape.com>, original author
  25.  *
  26.  * Alternatively, the contents of this file may be used under the terms of
  27.  * either the GNU General Public License Version 2 or later (the "GPL"), or
  28.  * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
  29.  * in which case the provisions of the GPL or the LGPL are applicable instead
  30.  * of those above. If you wish to allow use of your version of this file only
  31.  * under the terms of either the GPL or the LGPL, and not to allow others to
  32.  * use your version of this file under the terms of the MPL, indicate your
  33.  * decision by deleting the provisions above and replace them with the notice
  34.  * and other provisions required by the GPL or the LGPL. If you do not delete
  35.  * the provisions above, a recipient may use your version of this file under
  36.  * the terms of any one of the MPL, the GPL or the LGPL.
  37.  *
  38.  * ***** END LICENSE BLOCK ***** */
  39.  
  40. function initProfiler ()
  41. {
  42.     var prefs =
  43.         [
  44.          ["profile.template.xml", "chrome://venkman/locale/profile.xml.tpl"],
  45.          ["profile.template.html", "chrome://venkman/locale/profile.html.tpl"],
  46.          ["profile.template.csv", "chrome://venkman/locale/profile.csv.tpl"],
  47.          ["profile.template.txt", "chrome://venkman/locale/profile.txt.tpl"],
  48.          ["profile.ranges.default", "1000000, 5000, 2500, 1000, 750, 500, " +
  49.           "250, 100, 75, 50, 25, 10, 7.5, 5, 2.5, 1, 0.75, 0.5, 0.25"]
  50.         ];
  51.  
  52.     console.prefManager.addPrefs(prefs);
  53. }
  54.  
  55. function ProfileReport (reportTemplate, file, rangeList, scriptInstanceList)
  56. {
  57.     this.reportTemplate = reportTemplate;
  58.     this.file = file;
  59.     this.rangeList = rangeList;
  60.     this.scriptInstanceList = scriptInstanceList;
  61.     this.key = "total";
  62. }
  63.  
  64. console.profiler = new Object();
  65.  
  66. console.profiler.__defineSetter__ ("enabled", pro_setenable);
  67. function pro_setenable(state)
  68. {
  69.     if (state)
  70.         console.jsds.flags |= COLLECT_PROFILE_DATA;
  71.     else
  72.         console.jsds.flags &= ~COLLECT_PROFILE_DATA;
  73. }
  74.  
  75. console.profiler.__defineGetter__ ("enabled", pro_getenable);
  76. function pro_getenable(state)
  77. {
  78.     return Boolean(console.jsds.flags & COLLECT_PROFILE_DATA);
  79. }
  80.  
  81. console.profiler.summarizeScriptWrapper =
  82. function pro_sumscript (scriptWrapper, key)
  83. {
  84.     var ex;
  85.  
  86.     try
  87.     {
  88.         var jsdScript = scriptWrapper.jsdScript;
  89.         if (!jsdScript.isValid)
  90.             return null;
  91.         
  92.         var ccount = jsdScript.callCount;
  93.         if (!ccount)
  94.             return null;
  95.         
  96.         var tot_ms = roundTo(jsdScript.totalExecutionTime, 2);
  97.         var min_ms = roundTo(jsdScript.minExecutionTime, 2);
  98.         var max_ms = roundTo(jsdScript.maxExecutionTime, 2);
  99.         var avg_ms = roundTo(jsdScript.totalExecutionTime / ccount, 2);
  100.         var own_tot_ms = roundTo(jsdScript.totalOwnExecutionTime, 2);
  101.         var own_min_ms = roundTo(jsdScript.minOwnExecutionTime, 2);
  102.         var own_max_ms = roundTo(jsdScript.maxOwnExecutionTime, 2);
  103.         var own_avg_ms = roundTo(jsdScript.totalOwnExecutionTime / ccount, 2);
  104.         var recurse = jsdScript.maxRecurseDepth;
  105.  
  106.         var summary = new Object();
  107.         summary.total = tot_ms;
  108.         summary.ccount = ccount;
  109.         summary.avg = avg_ms;
  110.         summary.min = min_ms;
  111.         summary.max = max_ms;
  112.         summary.own_avg = own_avg_ms;
  113.         summary.own_min = own_min_ms;
  114.         summary.own_max = own_max_ms;
  115.         summary.own_total = own_tot_ms;
  116.         summary.recurse = recurse;
  117.         summary.url = jsdScript.fileName;
  118.         summary.file = getFileFromPath(summary.url);
  119.         summary.base = jsdScript.baseLineNumber;
  120.         summary.end = summary.base + jsdScript.lineExtent;
  121.         summary.fun = scriptWrapper.functionName;
  122.         var own_str = getMsg(MSN_FMT_PROFILE_STR2, [own_tot_ms, own_min_ms,
  123.                                                     own_max_ms, own_avg_ms]);
  124.         summary.str = getMsg(MSN_FMT_PROFILE_STR,
  125.                              [summary.fun, summary.base, summary.end, ccount,
  126.                               (summary.recurse ?
  127.                                getMsg(MSN_FMT_PROFILE_RECURSE, recurse) : ""),
  128.                               tot_ms, min_ms, max_ms, avg_ms, own_str]);
  129.         summary.key = summary[key];
  130.         return summary;
  131.     }
  132.     catch (ex)
  133.     {
  134.         /* This function is called under duress, and the script representd
  135.          * by |s| may get collected at any point.  When that happens,
  136.          * attempting to access to the profile data will throw this
  137.          * exception.
  138.          */
  139.         if ("result" in ex &&
  140.             ex.result == Components.results.NS_ERROR_NOT_AVAILABLE)
  141.         {
  142.             display (getMsg(MSN_PROFILE_LOST, formatScript(jsdScript)), MT_WARN);
  143.         }
  144.         else
  145.         {
  146.             dd ("rethrow");
  147.             dd (dumpObjectTree(ex));
  148.             throw ex;
  149.         }    
  150.     }
  151.  
  152.     return null;
  153. }
  154.  
  155. console.profiler.summarizeScriptInstance =
  156. function pro_suminst (scriptInstance, key)
  157. {
  158.     var summaryList = new Array();
  159.     var summary;
  160.     
  161.     if (scriptInstance.topLevel)
  162.         summary = this.summarizeScriptWrapper (scriptInstance.topLevel, key);
  163.     if (summary)
  164.         summaryList.push (summary);
  165.  
  166.     for (var f in scriptInstance.functions)
  167.     {
  168.         summary = this.summarizeScriptWrapper(scriptInstance.functions[f], key);
  169.         if (summary)
  170.             summaryList.push(summary);
  171.     }
  172.  
  173.     return summaryList;
  174. }
  175.  
  176. console.profiler.generateReportSection =
  177. function pro_rptinst (profileReport, scriptInstance, sectionData)
  178. {
  179.     function keyCompare (a, b)
  180.     {
  181.         if (a.key < b.key)
  182.             return 1;
  183.         if (a.key > b.key)
  184.             return -1;
  185.         return 0;
  186.     };
  187.  
  188.     function scale(K, x) { return roundTo(K * x, 2); };
  189.  
  190.     const MAX_WIDTH = 90;
  191.  
  192.     var summaryList = this.summarizeScriptInstance (scriptInstance,
  193.                                                     profileReport.key);
  194.     if (!summaryList.length)
  195.         return false;
  196.  
  197.     summaryList = summaryList.sort(keyCompare);
  198.  
  199.     var file = profileReport.file;
  200.     var reportTemplate = profileReport.reportTemplate;
  201.     var rangeList = profileReport.rangeList ? profileReport.rangeList : [1, 0];
  202.     var finalRangeIndex = rangeList.length - 1;
  203.     var previousRangeIndex;
  204.     var rangeIter = 0;
  205.     var rangeIndex = 0;
  206.     var K = 1;
  207.     var i;
  208.     
  209.     if (typeof summaryList[0].key == "number")
  210.     {
  211.         for (i = 0; i < rangeList.length; ++i)
  212.             rangeList[i] = Number(rangeList[i]);
  213.     }
  214.  
  215.     if ("sectionHeader" in reportTemplate)
  216.     {
  217.         file.write(replaceStrings(reportTemplate.sectionHeader,
  218.                                   sectionData));
  219.     }
  220.  
  221.     for (i = 0; i < summaryList.length; ++i)
  222.     {
  223.         var summary = summaryList[i];
  224.         var rangeData;
  225.         
  226.         while (summary.key &&
  227.                rangeIndex < finalRangeIndex &&
  228.                summary.key < rangeList[rangeIndex])
  229.         {
  230.             ++rangeIndex;
  231.         }
  232.  
  233.         if (previousRangeIndex != rangeIndex)
  234.         {
  235.             if (rangeIter > 0 && ("rangeFooter" in reportTemplate))
  236.             {
  237.                 file.write(replaceStrings(reportTemplate.rangeFooter,
  238.                                           rangeData));
  239.             }
  240.  
  241.             var maxRange = (rangeIndex > 0 ?
  242.                             rangeList[rangeIndex - 1] : summary.key);
  243.             var minRange = (rangeIndex < finalRangeIndex ? 
  244.                             rangeList[rangeIndex + 1] : summary.key);
  245.             K = MAX_WIDTH / maxRange;
  246.  
  247.             rangeData = {
  248.                 "\\$range-min"        : minRange,
  249.                 "\\$range-max"        : maxRange,
  250.                 "\\$range-number-prev": rangeIter > 0 ? rangeIter - 1 : 0,
  251.                 "\\$range-number-next": rangeIter + 1,
  252.                 "\\$range-number"     : rangeIter,
  253.                 "__proto__"           : sectionData
  254.             };
  255.  
  256.             if ("rangeHeader" in reportTemplate)
  257.             {
  258.                 file.write(replaceStrings(reportTemplate.rangeHeader,
  259.                                           rangeData));
  260.             }
  261.  
  262.             previousRangeIndex = rangeIndex;
  263.             ++rangeIter;
  264.         }
  265.  
  266.         var summaryData = {
  267.             "\\$item-number-next": i + 1,
  268.             "\\$item-number-prev": i - 1,
  269.             "\\$item-number"     : i,
  270.             "\\$item-name"       : summary.url,
  271.             "\\$item-summary"    : fromUnicode(summary.str, MSG_REPORT_CHARSET),
  272.             "\\$item-min-pct"    : scale(K, summary.min),
  273.             "\\$item-below-pct"  : scale(K, summary.avg - summary.min),
  274.             "\\$item-above-pct"  : scale(K, summary.max - summary.avg),
  275.             "\\$max-time"        : summary.max,
  276.             "\\$min-time"        : summary.min,
  277.             "\\$avg-time"        : summary.avg,
  278.             "\\$total-time"      : summary.total,
  279.             "\\$own-max-time"   : summary.own_max,
  280.             "\\$own-min-time"   : summary.own_min,
  281.             "\\$own-avg-time"   : summary.own_avg,
  282.             "\\$own-total-time" : summary.own_total,
  283.             "\\$call-count"      : summary.ccount,
  284.             "\\$recurse-depth"   : summary.recurse,
  285.             "\\$function-name"   : fromUnicode(summary.fun, MSG_REPORT_CHARSET),
  286.             "\\$start-line"      : summary.base,
  287.             "\\$end-line"        : summary.end,
  288.             "__proto__"          : rangeData
  289.         };
  290.  
  291.         if ("itemBody" in reportTemplate)
  292.             file.write(replaceStrings(reportTemplate.itemBody, summaryData));
  293.     }
  294.  
  295.     if ("rangeFooter" in reportTemplate)
  296.     {
  297.         /* close the final range */
  298.         file.write(replaceStrings(reportTemplate.rangeFooter,
  299.                                   rangeData));
  300.     }
  301.  
  302.     if ("sectionFooter" in reportTemplate)
  303.     {
  304.         file.write(replaceStrings(reportTemplate.sectionFooter,
  305.                                   sectionData));
  306.     }
  307.  
  308.     return true;
  309. }
  310.  
  311. console.profiler.generateReport =
  312. function pro_rptall (profileReport)
  313. {
  314.     var profiler = this;
  315.     var sectionCount = 0;
  316.     
  317.     function generateReportChunk (i)
  318.     {
  319.         /* we build the report in chunks, with setTimeouts in between,
  320.          * so the UI can come up for air. */
  321.         var scriptInstance = profileReport.scriptInstanceList[i];
  322.         var url = scriptInstance.url;
  323.         
  324.         var sectionData = {
  325.             "\\$section-number-prev": (sectionCount > 0) ? sectionCount - 1 : 0,
  326.             "\\$section-number-next": sectionCount + 1,
  327.             "\\$section-number"     : sectionCount,
  328.             "\\$section-link"       : (url ? "<a class='section-link' href='" +
  329.                                        url + "'>" + url + "</a>" : MSG_VAL_NA),
  330.             "\\$full-url"           : url,
  331.             "\\$file-name"          : getFileFromPath(url),
  332.             "__proto__"             : reportData
  333.         };
  334.         
  335.         var hadData = profiler.generateReportSection (profileReport,
  336.                                                       scriptInstance,
  337.                                                       sectionData);
  338.         if (++i == profileReport.scriptInstanceList.length)
  339.         {
  340.             if ("reportFooter" in reportTemplate)
  341.                 file.write(replaceStrings(reportTemplate.reportFooter,
  342.                                           reportData));
  343.             if ("onComplete" in profileReport)
  344.                 profileReport.onComplete(i);
  345.         }
  346.         else
  347.         {
  348.             if (hadData)
  349.             {
  350.                 ++sectionCount;
  351.                 console.status = getMsg(MSN_PROFILE_SAVING, [i, last]);
  352.                 setTimeout (generateReportChunk, 10, i);                
  353.             }
  354.             else
  355.             {
  356.                 generateReportChunk (i);
  357.             }
  358.         }   
  359.     };
  360.     
  361.     var reportData = {
  362.         "\\$report-charset": MSG_REPORT_CHARSET,
  363.         "\\$full-date"     : String(Date()),
  364.         "\\$user-agent"    : navigator.userAgent,
  365.         "\\$venkman-agent" : console.userAgent,
  366.         "\\$sort-key"      : profileReport.key
  367.     };
  368.  
  369.     var reportTemplate = profileReport.reportTemplate;
  370.     var file = profileReport.file;
  371.     
  372.     if ("reportHeader" in reportTemplate)
  373.         file.write(replaceStrings(reportTemplate.reportHeader, reportData));
  374.  
  375.     var length = profileReport.scriptInstanceList.length;
  376.     var last = length - 1;
  377.  
  378.     generateReportChunk (0);
  379. }
  380.  
  381. console.profiler.loadTemplate =
  382. function pro_load (url)
  383. {
  384.     var lines = loadURLNow(url);
  385.     if (!lines)
  386.         return null;
  387.  
  388.     var sections = {
  389.          "reportHeader"  : /@-section-start/mi,
  390.          "sectionHeader" : /@-range-start/mi,
  391.          "rangeHeader"   : /@-item-start/mi,
  392.          "itemBody"      : /@-item-end/mi,
  393.          "rangeFooter"   : /@-range-end/mi,
  394.          "sectionFooter" : /@-section-end/mi,
  395.          "reportFooter"  : 0
  396.     };
  397.  
  398.     var reportTemplate = parseSections (lines, sections);
  399.     
  400.     //dd(dumpObjectTree (reportTemplate));
  401.     return reportTemplate;
  402. }
  403.  
  404.